package edu.uts.reekie.designer.implementation.figures;

import org.eclipse.draw2d.ColorConstants;
import org.eclipse.draw2d.Figure;
import org.eclipse.draw2d.Graphics;
import org.eclipse.draw2d.LineBorder;
import org.eclipse.draw2d.Polygon;
import org.eclipse.draw2d.PolygonDecoration;
import org.eclipse.draw2d.RotatableDecoration;
import org.eclipse.draw2d.geometry.Dimension;
import org.eclipse.draw2d.geometry.Point;
import org.eclipse.draw2d.geometry.PointList;
import org.eclipse.draw2d.geometry.Rectangle;
import org.w3c.dom.css.Rect;

import sun.java2d.pipe.SolidTextRenderer;

public class PortDecoration extends Figure implements RotatableDecoration
 {
	
	int SIDE_LENGTH = 100;
	int BOX_SIDE_LENGTH = 20;
	
	// an empty decoration
	private class EmptyDecoration extends PolygonDecoration {
		
		public EmptyDecoration() {
			setTemplate(new PointList()); 
		}
		
	}
	
	RotatableDecoration innerDecoration; 
	Figure portBox;
	Point refPoint;
	
	
	/* */
	@Override
	public void setReferencePoint(Point p) {
		
		refPoint = p;
		
		if (innerDecoration!=null) {
			innerDecoration.setReferencePoint(p);
			innerDecoration.setLocation(getLocationOnPortBoxFromReferencePoint(p));
		}
		
	}
	
	public void setLocation(Point p) {
		
		super.setLocation(p.getTranslated(-SIDE_LENGTH/2,-SIDE_LENGTH/2));
		
		if (innerDecoration!=null) {
			innerDecoration.setLocation(p);
			
			
			portBox.setLocation(p.getTranslated(-BOX_SIDE_LENGTH/2,-BOX_SIDE_LENGTH/2));
		}
	}
	
	public void setScale(double x, double y) {
		/*
		if (innerDecoration!=null)
			innerDecoration.setScale(x,y);
			*/
	}
	
	public Point getLocationOnPortBoxFromReferencePoint(Point reference) {
		Rectangle r = Rectangle.SINGLETON;
		r.setBounds(portBox.getBounds());
		r.translate(-1, -1);
		r.resize(1, 1);

		this.translateToAbsolute(r);
		float centerX = r.x + 0.5f * r.width;
		float centerY = r.y + 0.5f * r.height;
		
		if (r.isEmpty() || (reference.x == (int)centerX && reference.y == (int)centerY))
			return new Point((int)centerX, (int)centerY);  //This avoids divide-by-zero

		float dx = reference.x - centerX;
		float dy = reference.y - centerY;
		
		//r.width, r.height, dx, and dy are guaranteed to be non-zero. 
		float scale = 0.5f / Math.max(Math.abs(dx) / r.width, Math.abs(dy) / r.height);

		dx *= scale;
		dy *= scale;
		centerX += dx;
		centerY += dy;

		return new Point(Math.round(centerX), Math.round(centerY));
	}
	
	public Rectangle getBounds() {
		return super.getBounds();
		
		
		/*
		if (portBox==null || innerDecoration==null)
			return super.getBounds();
		//return portBox.getBounds().union(innerDecoration.getBounds());
		return portBox.getBounds();
		*/
	}
	
	/*
	public Rectangle getBounds() {
		return portBox.getBounds().union(innerDecoration.getBounds());
	}
	*/

	
	public PortDecoration(RotatableDecoration decoration) {
		
		setFocusTraversable(false);
		
		if (decoration==null){
			SIDE_LENGTH = BOX_SIDE_LENGTH + 5;
		}
		
		// THIS
		this.setSize(SIDE_LENGTH,SIDE_LENGTH);
		this.setOpaque(false);
		this.setBorder(null);
		//this.setBorder(new LineBorder(ColorConstants.black,1));
		//this.setBackgroundColor(ColorConstants.white);
		//this.setForegroundColor(ColorConstants.white);
		
		/*
		if (decoration!=null)
			this.bounds = portBox.getBounds().expand(decoration.getBounds().height,decoration.getBounds().width);
		*/
		
		// THE PORT BOX
		portBox = new Figure();
		
		portBox.setSize(BOX_SIDE_LENGTH,BOX_SIDE_LENGTH);
		portBox.setOpaque(true);
		portBox.setBackgroundColor(ColorConstants.white);
		portBox.setBorder(new LineBorder(ColorConstants.black,1));
		portBox.setForegroundColor(ColorConstants.white);
		this.add(portBox);
		
		
		// THE INNER Decoration
		this.innerDecoration = decoration;
		if (innerDecoration==null){
			innerDecoration = new EmptyDecoration();
			/*
			innerDecoration.setTemplate(EmptyDecoration.TRIANGLE_TIP);
			innerDecoration.setFill(true);
			innerDecoration.setOpaque(true);
			innerDecoration.setScale(4, 4);
			innerDecoration.setEnabled(true);
			innerDecoration.setVisible(true);
			innerDecoration.setForegroundColor(ColorConstants.black);
			*/
		}
		this.add(innerDecoration);
	}
	
	

}
